package com.ef.service.impl;

import java.util.Date;
import java.util.List;

import org.hibernate.criterion.DetachedCriteria;
import org.hibernate.criterion.Order;
import org.hibernate.criterion.Restrictions;

import com.ef.constant.ELeadsClassStatus;
import com.ef.constant.ETimeline;
import com.ef.constant.StatusType;
import com.ef.dao.LeadsClassEntityDao;
import com.ef.domain.ClassEntity;
import com.ef.domain.Leads;
import com.ef.domain.LeadsClassEntity;
import com.ef.service.LeadsClassEntityService;
import com.ef.util.CustomExample;
import com.ef.util.PaginationSupport;

public class LeadsClassEntityServiceImpl extends BaseServiceImpl implements
		LeadsClassEntityService {

	private LeadsClassEntityDao leadsClassEntityDao;

	public LeadsClassEntity findById(Long id) {
		return leadsClassEntityDao.findById(id);
	}

	public LeadsClassEntityDao getLeadsClassEntityDao() {
		return leadsClassEntityDao;
	}

	public void setLeadsClassEntityDao(LeadsClassEntityDao leadsClassEntityDao) {
		this.leadsClassEntityDao = leadsClassEntityDao;
	}

	public List<LeadsClassEntity> getLeadsClassEntityListOrderByBookingTime(
			int year, int week, Leads leads) {
		return leadsClassEntityDao.getLeadsClassEntityListOrderByBookingTime(
				year, week, leads);
	}

	public List<LeadsClassEntity> getLeadsClassEntityListOrderByBookingTime(
			Leads leads, int num) {
		return leadsClassEntityDao.getLeadsClassEntityListOrderByBookingTime(
				leads, num);
	}

	public List<LeadsClassEntity> getLeadsClassEntityListWithClassEntity(
			ClassEntity classEntity) {
		return leadsClassEntityDao
				.getLeadsClassEntityListWithClassEntity(classEntity);
	}

	public List<LeadsClassEntity> getLeadsClassEntityListWithClassEntityOrderByElitCard(
			ClassEntity classEntity) {
		return leadsClassEntityDao
				.getLeadsClassEntityListWithClassEntityOrderByElitCard(classEntity);
	}

	public boolean leadsHasThisClassEntity(Long classEntityid, Long leadsid) {
		return leadsClassEntityDao.leadsHasThisClassEntity(classEntityid,
				leadsid);
	}

	public List<LeadsClassEntity> getLeadsClassEntityList(Leads leads, int max) {
		return leadsClassEntityDao.getLeadsClassEntityList(leads, max);
	}

	public PaginationSupport<LeadsClassEntity> findByClassEntityId(
			Long entityId, boolean isWaiting, int startIndex, int pageSize) {
		DetachedCriteria criterion = DetachedCriteria
				.forClass(LeadsClassEntity.class);
		criterion.createCriteria("classEntity").add(
				Restrictions.eq("id", entityId));
		if (isWaiting) {
			criterion.add(Restrictions.eq("classStatus",
					ELeadsClassStatus.WAITING));
		}
		criterion.addOrder(Order.asc("bookingTime"));
		return leadsClassEntityDao.findPageByCriteria(criterion, startIndex,
				pageSize);
	}

	public PaginationSupport<LeadsClassEntity> findByDate(Date date,
			boolean isWaiting, int startIndex, int pageSize) {
		DetachedCriteria criterion = DetachedCriteria
				.forClass(LeadsClassEntity.class);
		if (isWaiting) {
			criterion.add(Restrictions.eq("classStatus",
					ELeadsClassStatus.WAITING));
		}
		criterion.createCriteria("classEntity", "classEntity").add(
				Restrictions.eq("classDate", date)).add(
				Restrictions.eq("status", StatusType.VALID));
		criterion.addOrder(Order.desc("classEntity.classDate")).addOrder(
				Order.asc("classEntity.classTime")).addOrder(
				Order.asc("classEntity.id"))
				.addOrder(Order.desc("bookingTime"));
		return leadsClassEntityDao.findPageByCriteria(criterion, startIndex,
				pageSize);
	}

	public PaginationSupport<LeadsClassEntity> findByDateTime(Date date,
			ETimeline timeline, boolean isWaiting, int startIndex, int pageSize) {
		DetachedCriteria criterion = DetachedCriteria
				.forClass(LeadsClassEntity.class);
		if (isWaiting) {
			criterion.add(Restrictions.eq("classStatus",
					ELeadsClassStatus.WAITING));
		}
		criterion.createCriteria("classEntity", "classEntity").add(
				Restrictions.eq("classDate", date)).add(
				Restrictions.eq("classTime", timeline)).add(
				Restrictions.eq("status", StatusType.VALID));
		criterion.addOrder(Order.desc("classEntity.classDate")).addOrder(
				Order.asc("classEntity.classTime")).addOrder(
				Order.asc("classEntity.id"))
				.addOrder(Order.desc("bookingTime"));
		return leadsClassEntityDao.findPageByCriteria(criterion, startIndex,
				pageSize);
	}

	public PaginationSupport<LeadsClassEntity> findByExample(
			CustomExample<LeadsClassEntity> example, int startIndex,
			int pageSize) {
		return leadsClassEntityDao.findPageByExample(example, startIndex,
				pageSize);
	}

	public PaginationSupport<LeadsClassEntity> findByLeadIdBetweenDays(
			Long leadsId, Date fDate, Date lDate, int startIndex, int pageSize) {
		DetachedCriteria criterion = DetachedCriteria
				.forClass(LeadsClassEntity.class);
		criterion.createCriteria("leads").add(Restrictions.eq("id", leadsId));
		criterion.createCriteria("classEntity", "classEntity").add(
				Restrictions.ge("classDate", fDate)).add(
				Restrictions.le("classDate", lDate)).add(
				Restrictions.eq("status", StatusType.VALID));
		criterion.addOrder(Order.asc("classEntity.classDate")).addOrder(
				Order.asc("classEntity.classTime")).addOrder(
				Order.asc("classEntity.id"))
				.addOrder(Order.desc("bookingTime"));
		return leadsClassEntityDao.findPageByCriteria(criterion, startIndex,
				pageSize);

	}
}
